iT邦幫忙

2022 iThome 鐵人賽

DAY 16
0
Modern Web

Node.js系列 第 16

WebSocket

  • 分享至 

  • xImage
  •  

DAY 16 WebSocket

tags: 第 14 屆 iThome 鐵人賽 (2022)

WebSocket模組

WebSocket是HTML 5 開始提供的一種瀏覽器與伺服器間進行全雙工通訊的網路技術。在WebSocketAPI中,瀏覽器和伺服器只需要一次驗證,之後瀏覽器和伺服器之間就形成了一條快速通道,瀏覽器和伺服器之間直接可以互相傳送資料了。

{%hackmd BJrTq20hE %}

要使用WebSocket,關鍵在於伺服器端的支援,這樣才有可能用支援WebSocket的瀏覽器使用WebSocket。

  • (1) 在Node.js中,ws是使用很廣泛的WebSocket模組,首先在package.json中增加ws的依賴:
"dependencies": {
    "ws": "^8.8.1"
  }

執行npm install後,我們就可以在app.js中撰寫WebSocket的伺服器端程式。

npm install ws
  • (2)建立一個WS的伺服器
const WebSocket = require('ws');
const WebSocketServer = WebSocket.Server;
const wss = new WebSocketServer({
    port:3000
});
  • (3)接下來,如果有WebSocket請求連線,wss物件可以回應connection事情來處理這個WebSocket
wss.on('connection', function (ws) {
  console.log(`[SERVER] connection()`);
  ws.on('message', function (message) {
    console.log(`[SERVER] Received: ${message}`);
    setTimeout(() => {
      ws.send(`你的名字是?`, (err) => {
        if (err) {
          console.log(`[SERVER] error: ${err}`);
        }
      });
    }, 1000);
  })
});

在 connection 事件中,回呼函數會傳入一個 WS 實例 , 表示這個WebSocket連接。對於每個WS連接,我們都要對它綁定某些事情方法來處理不同的事情。這裡,我們回應message事情,在收到訊息後再傳回一個 ECHO:xxx的訊息給用戶端

  • (4)接下來建立WebSocket連接。在命令列執行npm start。在目前頁面下,直接開啟可以執行JS程式的瀏覽器Console,依次輸入程式:
// 開啟一個WebSocket
let count = 0;

let ws = new WebSocket('ws://localhost:3000/ws/chat');

ws.on('open', function () {
  console.log(`[CLIENT] open()`);
  ws.send('Hello!');
});

ws.on('message', function (message) {
  console.log(`[CLIENT] Received: ${message}`);
  count++;
  if (count > 3) {
    ws.send('Goodbye!');
    ws.close();
  } else {
    setTimeout(() => {
      ws.send(`嗨,我是${count}號!`);
    }, 1000);
  }
});

結論:

在 Node 環境下,ws模組的用戶端可以用測試伺服器程式,不然每次都必須在瀏覽器上執行JS程式。
從上面的測試可以看出,WebSocket協定本身不要求相同來源策略,WS也讓我們能夠建立起一個網站,雖然比Express還要複雜了些,但只是依次的驗證就讓用戶端和伺服器能夠交換資料,下一篇 「DAY 17 HTTP」將會教我們如何做出一個漂亮的網站拉ˋˇˊ!


上一篇
DAY 15 知名DC機器人該有的3個功能
下一篇
DAY 17 建構網頁的第一步『Http模組』
系列文
Node.js30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言